#include <stdlib.h>

#include "lib.h"

#include "slotguts.h"
#include "crazydragonguts.h"
#include "crazydragoncommon.h"
#include "slotspin.h"

bool8 
CrazyDragonSlotGuts::isValidGuts()
{
    return ((getGutsId() >= 800) && (getGutsId() <= 899)) ;
}


SlotSpin *
CrazyDragonSlotGuts::makeJackpot()
{
    uint8 *stops = new uint8[getReelCount()];
    SlotSpin *spin = new SlotSpin();

    spin->setBet(3);
    spin->addLine(1);

    /**
     * Hard set the reels to jackpots.  The assumption is
     * that the jackpot icon is the second to last icon on
     * the strip.  Unlike GTBB this strip ends in an Icon.
     */
    for (uint8 i = 0; i < getReelCount(); i++)
    {
//        stops[i] = getIcon(i, getIconCount(i) - 1)->position;
        stops[i] = 16;
    }

    spin->setStops(getReelCount(), stops);

    classifyResult(spin);
    spin->setSpinComplete(true);
 
    m_spins.push_back(spin);

    delete [] stops;

    return spin;
}



void
CrazyDragonSlotGuts::spin(SlotSpin *slotSpin)
{
    SlotGuts::spin(slotSpin);
    SpinLine *spinLine = slotSpin->getSpinLineAt(0);

    m_respins = 0;
	int32 total_respins = -1;
    do
    {
		total_respins++;
        // Check for a jackpot.
        if ( total_respins >= CrazyDragonCommon::RESPIN_JACKPOT )
        {
            makeJackpot();
            m_respins = 0;
			total_respins = 0;
        }
        else
        {
            /**
             * If we have a respin count we know this
             * is not the first time through.  In that
             * case we know we need to created a new spin
             * and set it up as a respin.
             */
            if ( m_respins > 0 )
            {
                slotSpin = new SlotSpin();
        
                slotSpin->setBet(0);
                slotSpin->setBonusGameType(0);
                slotSpin->addLine(1);
                SlotGuts::spin(slotSpin);
                spinLine = slotSpin->getSpinLineAt(0);
                m_respins--;
            }
    
            // Check for more accumulated respsins
            if ( slotSpin->getBet() == 0 || slotSpin->getBet() == getBetCount() )
            {
                if ( spinLine->payouttypeid == CrazyDragonCommon::EVT_DRAGONHEAD )
                {
                    m_respins += CrazyDragonCommon::RESPIN_DRAGONHEAD;
                }
                else if ( spinLine->payouttypeid == CrazyDragonCommon::EVT_DRAGONBODY )
                {
                    m_respins += CrazyDragonCommon::RESPIN_DRAGONBODY;
                }
                else if ( spinLine->payouttypeid == CrazyDragonCommon::EVT_DRAGONTAIL )
                {
                    m_respins += CrazyDragonCommon::RESPIN_DRAGONTAIL;
                }
            }
        }


    } while ( (m_respins > 0 ) && (!m_hardMalfunction));

}



uint8
CrazyDragonSlotGuts::classifyStops(uint8* stops,uint8 bet, uint8 line)
{
	uint8 result = CrazyDragonCommon::EVT_LOSER;
    uint8 pagodas = 0;
    uint8 yingyangs = 0;
    uint8 bonzais = 0;
    uint8 firecrackers = 0;
    uint8 coi = 0;
	uint8 cdjackpot = 0;

    /**
     * Count up the icons and see what we have.
     */
    for ( uint8 reelid = 0; reelid < this->getReelCount(); reelid++ )
    {
        switch ( getIcon(reelid, stops[reelid])->iconid )
        {
            case CrazyDragonCommon::PAGODA:
                pagodas++;
                break;

            case CrazyDragonCommon::YINGYANG:
                yingyangs++;
                break;

            case CrazyDragonCommon::BONZAI:
                bonzais++;
                break;

            case CrazyDragonCommon::FIRECRACKER:
                firecrackers++;
                break;

            case CrazyDragonCommon::COI:
                coi++;
                break;

			case CrazyDragonCommon::CDJACKPOT:
				cdjackpot++;
				break;

        }
    }

    /**
     * Check for the 3 of each winners.  Note the Ying Yang is wild.  Since 3 Ying Yang
     * equal 3 Coi we have to check the Coi first.
     */

    if ( result == CrazyDragonCommon::EVT_LOSER && (coi == getReelCount()  || (coi + yingyangs) == getReelCount()) )
    {
        result = CrazyDragonCommon::EVT_3COI;
    }

    if ( result == CrazyDragonCommon::EVT_LOSER && (pagodas == getReelCount()  || (pagodas + yingyangs) == getReelCount()) )
    {
        result = CrazyDragonCommon::EVT_3PAGODAS;
    }

    if ( result == CrazyDragonCommon::EVT_LOSER && (bonzais == getReelCount()  || (bonzais + yingyangs) == getReelCount()) )
    {
        result = CrazyDragonCommon::EVT_3BONZAIS;
    }

    if ( result == CrazyDragonCommon::EVT_LOSER && (firecrackers == getReelCount()  || (firecrackers + yingyangs) == getReelCount()) )
    {
        result = CrazyDragonCommon::EVT_3FIRECRACKERS;
    }

    if ( result == CrazyDragonCommon::EVT_LOSER && getIcon(0, stops[0])->iconid == CrazyDragonCommon::DRAGONHEAD )
    {
        if ( getIcon(1, stops[1])->iconid == CrazyDragonCommon::DRAGONBODY )
        {
            if ( getIcon(2, stops[2])->iconid == CrazyDragonCommon::DRAGONTAIL )
            {
                result = CrazyDragonCommon::EVT_DRAGONTAIL;
            }
            else
            {
                result = CrazyDragonCommon::EVT_DRAGONBODY;
            }
        }
        else
        {
            result = CrazyDragonCommon::EVT_DRAGONHEAD;
        }
    }

    if ( result == CrazyDragonCommon::EVT_LOSER && cdjackpot == getReelCount())
    {
        result = CrazyDragonCommon::EVT_CDJACKPOT;
    }


	return result;
}


